﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using static System.Threading.Thread;
using static System.Console;

namespace Project_1
{
    /// <summary>
    /// 1.11 使用Monitor类锁定资源
    /// </summary>
    public class Unit_1_11
    {
        /*
          lock是Monitor的简洁写法，
          使用Monitor.TryEnter(lock,TimeSpan) 可以避免死锁问题
          
          if (Monitor.TryEnter(lock1, TimeSpan.FromSeconds(5)))
          {
              WriteLine("成功获得受保护的资源");
          }
          else
          {
              WriteLine("获取资源超时");
          }
         */
        public static void Go()
        {
            object lock1=new object();
            object lock2=new object();

            new Thread(()=> LookTooMuch(lock1,lock2)).Start();

            lock (lock2)
            {
                Sleep(1000);
                WriteLine("监视器TryEnter允许不被卡住，在指定的超时时间过后返回false");
                if (Monitor.TryEnter(lock1, TimeSpan.FromSeconds(5)))
                {
                    WriteLine("成功获得受保护的资源");
                }
                else
                {
                    WriteLine("获取资源超时");
                }
            }

            // new Thread(()=> LookTooMuch(lock1,lock2)).Start();
            //WriteLine("-----------------------");
            //
            //lock (lock2)
            //{
            //    WriteLine("这将是一个死锁");
            //    Sleep(200);
            //    lock (lock1)
            //    {
            //        WriteLine("成功获得受保护的资源");
            //    }
            //    WriteLine("死锁，前面卡住，不会执行到这里");
            //}
        }

        static void LookTooMuch(object lock1,object lock2)
        {
            lock (lock1)
            {
                Sleep(1000);
                lock (lock2) ;
            }
        }
    }
}
